package pe.com.certicom.ittsa.model.dao;

import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.util.List;

import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;

import pe.com.certicom.ittsa.control.util.KMLReader;
import pe.com.certicom.ittsa.framework.dat.Conexion;
import pe.com.certicom.ittsa.framework.dat.DaoHelper;
import pe.com.certicom.ittsa.model.bean.BeanBusMapa;
import pe.com.certicom.ittsa.model.bean.BeanCoordenadas;
import pe.com.certicom.ittsa.model.bean.BeanGeoCode;

public class MapaDao {
	private static final Log log = LogFactory.getLog(DispAsientoDAO.class);
	
	public static List<BeanBusMapa> obtenerBuses(String origen, String destino, String fecha) throws Exception{		
		List<BeanBusMapa> lstBuses = null;		
		Object[] objParametros =  new Object[]{
				origen,destino,fecha
		};
		BeanBusMapa bean;
		BeanCoordenadas coordenadasactual;
		BeanGeoCode ubicacion;
		String tiempoaprox;
		log.info("Inicio obtenerBuses");
		lstBuses = DaoHelper.datoLista("Exe_cer_sis_sp_consulta_servicios",BeanBusMapa.class, objParametros);
		
		if(lstBuses.size()==0){
			throw new Exception("No hay informacion sobre la ruta indicada");
		}
		
		for(int i=0; i<lstBuses.size(); i++){
			bean = lstBuses.get(i);
        	if(bean==null){
        		throw new Exception("Error al obtener el vehiculo");
        	}
        	else{
    			coordenadasactual = getUbicacion(bean.getCodbus().toString());
            	bean.setCoord_x_actual(coordenadasactual.getCoord_x());
            	bean.setCoord_y_actual(coordenadasactual.getCoord_y());
            	bean.setGrados(coordenadasactual.getGrados());
            	ubicacion = getUbicacionFisica(coordenadasactual.getCoord_x(),coordenadasactual.getCoord_y());
            	bean.setUbicacion(ubicacion.getDireccion() + " " + ubicacion.getDistrito() + " " + ubicacion.getProvincia() + " " + ubicacion.getDepartamento());
            	
        		if(bean.getCoord_x()==null){
        			throw new Exception("No existen coordenada X registrada");
        		}
        		if(bean.getCoord_y()==null){
        			throw new Exception("No existen coordenada Y registrada");
        		}
        		if(bean.getVelocidad()==null){
        			throw new Exception("No existen velocidad registrada");
        		}
            	tiempoaprox = getTiempoAprox(bean.getCoord_x().toString(), bean.getCoord_y().toString(), coordenadasactual, bean.getVelocidad().toString());
            	bean.setTiempoaprox(tiempoaprox);
        	}
		}
		log.info("Fin obtenerBuses");
	
        return lstBuses;
	}

	private static String getTiempoAprox(String coord_x_destino, String coord_y_destino,
			BeanCoordenadas coordenadasactual, String velocidad) {		
		double tiempo = 0;
		double d_velocidad = velocidad!=null? Double.parseDouble(velocidad):0; 
		String distancia = getDistancia(coord_x_destino,coord_y_destino,coordenadasactual.getCoord_x(), coordenadasactual.getCoord_y());
		distancia = (distancia.indexOf("E-")!=-1)?"0": distancia;
		double d_distancia = distancia!=null? Double.parseDouble(distancia):0;
		d_distancia = Math.rint(d_distancia*1000)/1000;
		tiempo = (d_distancia/d_velocidad)*60;
		int mins = (int) tiempo;
		return mins + "";
	}

	private static String getDistancia(String coord_x_destino, String coord_y_destino, String coord_x_actual, String coord_y_actual) {
		Conexion conpost =	new Conexion();
		Connection con = null;
        PreparedStatement pst = null;
        ResultSet rst = null;
        String distancia = "0";
		String sql = "select (acos(sin(radians(" + coord_x_destino + ")) * sin(radians(" + coord_x_actual + ")) + " +  
                " cos(radians(" + coord_x_destino + ")) * cos(radians(" + coord_x_actual + ")) * "  + 
                " cos(radians(" + coord_y_destino + ") - radians(" + coord_y_actual + "))) * 6378) "  + 
                " as distancia_recorrida" ;
        try{
        	con = conpost.conectarPosgressGPS();
        	pst = con.prepareStatement(sql);
        	rst = pst.executeQuery();
        	
            while(rst.next()) {            	
            	distancia = rst.getString(1);
            }
        }
        catch (Exception e) {
			e.printStackTrace();
		} finally{
			conpost.desconectar(rst, pst, con);
		}
		return distancia;
	}

	private static BeanCoordenadas getUbicacion(String codbus) throws Exception {
		Conexion conpost =	new Conexion();
		Connection con = null;
        PreparedStatement pst = null;
        ResultSet rst = null;
        String sql = null;        
        BeanCoordenadas coordenadas = null;
        try{
        	con = conpost.conectarPosgressGPS();
			sql = "select co_coordx,co_coordy,r.di_grados from vehiculo v inner join recorrido r on(v.id_max_reco=r.id_reco) where v.id_emp='104' and no_vehi=? "; 
	        pst = con.prepareStatement(sql);
	        pst.setString(1,codbus);
            rst = pst.executeQuery();
            coordenadas = new BeanCoordenadas();
            while(rst.next()) {
            	coordenadas.setCoord_x(rst.getString(1));
            	coordenadas.setCoord_y(rst.getString(2));
            	coordenadas.setGrados(rst.getString(3));            	
            }
        }
        catch (Exception e) {
			e.printStackTrace();
		} finally{
			conpost.desconectar(rst, pst, con);
		}
        
		return coordenadas;
	}
	
	private static BeanGeoCode getUbicacionFisica(String x, String y) throws Exception{
        // Obtener direccion fisica
		BeanGeoCode bgeocode = null;
		bgeocode = KMLReader.readKML(x,y);
        while(bgeocode.getFlag()==1){
            bgeocode = KMLReader.readKML(x,y);
        }
        return bgeocode;
	}
}
